package com.example.fqapp.ui

import android.content.Intent
import androidx.appcompat.app.AppCompatActivity
import android.os.Bundle
import android.text.Editable
import android.text.TextWatcher
import android.util.Patterns
import android.view.View
import android.widget.Toast
import androidx.annotation.StringRes
import androidx.lifecycle.MutableLiveData
import androidx.lifecycle.Observer
import com.example.fqapp.R
import com.example.fqapp.application.MyApplication
import com.example.fqapp.bean.ApiResTest
import com.example.fqapp.data.LoginFormState
import com.example.fqapp.data.LoginResult
import com.example.fqapp.databinding.ActivityLoginBinding
import com.example.fqapp.model.ViewModelLogin
import com.example.fqapp.retrofit2.ApiUtil
import com.example.fqapp.room.entity.EntityUser
import retrofit2.Call
import retrofit2.Callback
import retrofit2.Response
import timber.log.Timber

class LoginActivity : AppCompatActivity() {
    private var myApplication: MyApplication = MyApplication.instance
    private lateinit var binding: ActivityLoginBinding
    private lateinit var viewModelLogin: ViewModelLogin

    override fun onCreate(savedInstanceState: Bundle?) {
        super.onCreate(savedInstanceState)

        binding = ActivityLoginBinding.inflate(layoutInflater)
        setContentView(binding.root)

        Timber.d("LoginActivity, onCreate(), enter")
        initViewModelLogin()
        initView()


        binding.btTest.setOnClickListener {
            Timber.d("onCreate(), btTest on click")
            ApiUtil.service.getTest("123456").enqueue(object : Callback<ApiResTest> {
                override fun onResponse(call: Call<ApiResTest>, response: Response<ApiResTest>) {
                    val apiResTest = response.body()
                    if (apiResTest == null) {
                        Timber.d("onCreate(), apiResTest is null")
                        return
                    }
                    Timber.d("onCreate(), apiResTest.data=%s", apiResTest.data)
                }

                override fun onFailure(call: Call<ApiResTest>, t: Throwable) {
                    t.printStackTrace()
                    Timber.d("onCreate(), getTest fail")
                }
            })
        }


        binding.btInsert.setOnClickListener {
            Timber.d("onCreate(), btInsert on click")
            insertUser()
        }
        binding.btQuery.setOnClickListener {
            Timber.d("onCreate(), btQuery on click")
            queryUser()
        }
    }

    private fun initView() {
        val phoneNum = binding.phoneNum
        val password = binding.password
        val btLogin = binding.btLogin
        val loading = binding.loading

        phoneNum.addTextChangedListener(object : TextWatcher {
            override fun beforeTextChanged(p0: CharSequence?, p1: Int, p2: Int, p3: Int) {

            }

            override fun onTextChanged(p0: CharSequence?, p1: Int, p2: Int, p3: Int) {

            }

            override fun afterTextChanged(p0: Editable?) {
                val currentText = p0.toString()
                Timber.d("account, afterTextChanged(), currentText=%s", currentText)
                // 文本改变后的操作
                setLiveDataLoginFormState()

            }

        })

        password.addTextChangedListener(object : TextWatcher {
            override fun beforeTextChanged(p0: CharSequence?, p1: Int, p2: Int, p3: Int) {

            }

            override fun onTextChanged(p0: CharSequence?, p1: Int, p2: Int, p3: Int) {

            }

            override fun afterTextChanged(p0: Editable?) {
                val currentText = p0.toString()
                Timber.d("afterTextChanged(), currentText=%s", currentText)
                setLiveDataLoginFormState()
            }
        })

        btLogin.setOnClickListener {
            if (!isPhoneNumValid(binding.phoneNum.text.toString())) {
                binding.phoneNum.error = getString(R.string.invalid_phone_num)
                return@setOnClickListener
            }
            if (!isPasswordValid(binding.password.text.toString())) {
                binding.password.error = getString(R.string.invalid_password)
                return@setOnClickListener
            }
            loading.visibility = View.VISIBLE
            login(phoneNum.text.toString(), password.text.toString())
        }
    }

    private fun setLiveDataLoginFormState() {
        var stringPhoneNum: String = binding.phoneNum.text.toString()
        Timber.d("LoginActivity, setLiveDataLoginFormState(), stringPhoneNum=%s", stringPhoneNum)
        var stringPassword: String = binding.password.text.toString()
        Timber.d("LoginActivity, setLiveDataLoginFormState(), stringPassword=%s", stringPassword)
        viewModelLogin.liveDataLoginFormState.value =
            LoginFormState(
                usernameError = R.string.invalid_phone_num,
                isHavePhoneNum = stringPhoneNum.isNotBlank(),
                isHavePassword = stringPassword.isNotBlank()
            )

    }

    private fun initViewModelLogin() {
        viewModelLogin = ViewModelLogin()
        viewModelLogin.liveDataLoginFormState.observe(this, Observer {
            Timber.d("LoginActivity, onCreate(), liveDataLoginFormState change")
            binding.btLogin.isEnabled = it.isHavePhoneNum && it.isHavePassword

        })
        viewModelLogin.liveDataLoginResult.observe(this, Observer {
            binding.loading.visibility = View.GONE
            if (it.success) {
                showLoginResult(R.string.login_success)

                val intent = Intent(this, MainActivity::class.java)
                startActivity(intent)
            } else {
                showLoginResult(it.error)
            }
        })
    }

    //查询用户
    private fun queryUser() {
        val thread = Thread {
            Timber.d("queryUser(), thread start")
            var phoneNum: String = "00000000000"
            var entityUser = myApplication.fqDatabase.daoUser().getUserByPhoneNum(phoneNum)
            if (entityUser == null) {

                runOnUiThread {
                    binding.txTips.text = "查询失败"
                };
            } else {
                runOnUiThread {
                    var temp = "查询成功，name=" + entityUser.name
                    binding.txTips.text = temp
                };
            }
            Thread.sleep(2000)
            runOnUiThread {
                binding.txTips.text = ""
            };
        }
        thread.start()
    }

    //插入用户
    private fun insertUser() {
        val thread = Thread {
            Timber.d("insertUser(), thread start")
            var entityUser: EntityUser = EntityUser()
            entityUser.name = "测试1"
            entityUser.phoneNum = "00000000000"
            entityUser.password = "123456"

            var tempUser = myApplication.fqDatabase.daoUser().getUserByPhoneNum(entityUser.phoneNum)
            if (tempUser != null) {
                runOnUiThread {
                    var temp = "用户已存在"
                    binding.txTips.text = temp
                };
            } else {

                var ret = myApplication.fqDatabase.daoUser().insert(entityUser)
                if (ret > 0) {
                    runOnUiThread {
                        binding.txTips.text = "插入成功"
                    };
                } else {
                    runOnUiThread {
                        binding.txTips.text = "插入失败"
                    };
                }
            }
            Thread.sleep(2000)
            runOnUiThread {
                binding.txTips.text = ""
            };
        }
        thread.start()
    }

    // A placeholder phoneNum validation check
    private fun isPhoneNumValid(phoneNum: String): Boolean {
        if (phoneNum.isEmpty()) {
            return false
        } else if (phoneNum.length != 11) {
            return false
        }
        return true
    }

    // A placeholder password validation check
    private fun isPasswordValid(password: String): Boolean {
        return password.length > 5
    }

    private fun login(account: String, password: String) {
        if (account.equals("abc")) {
            viewModelLogin.liveDataLoginResult.value =
                LoginResult(success = true, error = R.string.login_success)
        } else {
            viewModelLogin.liveDataLoginResult.value =
                LoginResult(success = false, error = R.string.login_failed)
        }
    }

    private fun showLoginResult(@StringRes errorString: Int) {
        Toast.makeText(applicationContext, errorString, Toast.LENGTH_SHORT).show()
    }
}